/*******************************************************************************
 * File name  : thread_watchdog.c
 *------------------------------------------------------------------------------
 * Project    : common
 *------------------------------------------------------------------------------
 * Author(s)  : Jimmy.Cui
 *------------------------------------------------------------------------------
 * Copyright (c) 2021 Jimmy.
 * All rights reserved.
 *******************************************************************************/

/********************************************************************************
 * Included header
 *******************************************************************************/
#include <stdio.h>
#include <stdlib.h>
#include "thread_watchdog.h"

/********************************************************************************
 * Local constants and macros (private to module)
 *******************************************************************************/

/********************************************************************************
 * Local data types (private typedefs / structs / enums)
 *******************************************************************************/

/********************************************************************************
 * Local data (private to module)
 *******************************************************************************/
static threadWd *sHead = NULL;

/********************************************************************************
 * Local function prototypes (private to module)
 *******************************************************************************/

/********************************************************************************
 * Global data (private to projection)
 *******************************************************************************/

/********************************************************************************
 * Local functions (private to module)
 *******************************************************************************/

/********************************************************************************
 * Local functions (extern)
 *******************************************************************************/
void threadWd_Create(threadWd **pp)
{
    threadWd *pThreadWd = NULL;
    threadWd *pTmp = sHead;

    pThreadWd = (threadWd *)malloc(sizeof(threadWd));
    pThreadWd->eWdStatus = E_FEED_DOG;
    pThreadWd->next = NULL;
    if (sHead == NULL)
    {
        sHead = pThreadWd;
    }
    else
    {
        while (pTmp->next != NULL)
        {
            pTmp = pTmp->next;
        }
        pTmp->next = pThreadWd;
    }
    *pp = pThreadWd;
}

void threadWd_FeedDog(threadWd *p)
{
    p->eWdStatus = E_FEED_DOG;
}

void threadWd_Exit(threadWd **pp)
{
    threadWd *pb = sHead;
    threadWd *pf = pb;

    if (sHead == NULL)
    {
        return;
    }
    while (pb != *pp && pb->next != NULL)
    {
        pf = pb;
        pb = pb->next;
    }
    if (pb == *pp)
    {
        if (pb == sHead)
        {
            sHead = pb->next;
        }
        else
        {
            pf->next = pb->next;
        }
        free(pb);
        *pp = NULL;
    }
}

void threadWd_Check(void)
{
    threadWd *pTmp = sHead;

    while (pTmp != NULL)
    {
        if (pTmp->eWdStatus == E_CLEAN)
        {
            exit(-1);
        }
        pTmp->eWdStatus = E_CLEAN;
        pTmp = pTmp->next;
    }
}

/*---------------------------------- End of the file ---------------------------------*/
